package cn.ly.core.concurrent;

import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.concurrent.CyclicBarrier;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

public class CyclicBarrierTest {
	//徒步需要时间：深圳，广东，邵阳，长沙，武汉
	private static int[] timeWalk = { 5, 8, 15, 15, 10 };
	//自驾
	private static int[] timeSelf = { 1, 3, 4, 4, 5 };
	//旅游大巴
	private static int[] timeBus = { 2, 4, 6, 6, 7 };
	
	static String now(){
		SimpleDateFormat sdf = new SimpleDateFormat("HH:mm:ss");
		return sdf.format(new Date()) + ": ";
	}
	
	static class Tour implements Runnable{
		private int[] times;
		private CyclicBarrier barrier;
		private String tourName;
		public Tour(int[] times,CyclicBarrier barrier,String tourName){
			this.times = times;
			this.barrier = barrier;
			this.tourName = tourName;
		}
		public void run() {
			try{
				Thread.sleep(times[0]*1000);
				System.out.println(now() + tourName + " Reached 深圳"); //这三个线程必须使用的是一个CyclicBarrier
				barrier.await();                                        //当一个线程到达CyclicBarrier的await()时，它会等待其它线程的执行
				Thread.sleep(times[1]*1000);                            //直到3个线程都到达同一个CyclicBarrier的await()的点
				System.out.println(now() + tourName + " Reached 广东");
				barrier.await();
				Thread.sleep(times[2]*1000);
				System.out.println(now() + tourName + " Reached 邵阳");
				barrier.await();
				Thread.sleep(times[3]*1000);
				System.out.println(now() + tourName + " Reached 长沙");
				barrier.await();
				Thread.sleep(times[4]*1000);
				System.out.println(now() + tourName + " Reached 武汉");
				barrier.await();
			}catch(Exception e){
				e.printStackTrace();
			}
		}
	}
	
	public static void main(String[] args) {
		//三个旅行团
		CyclicBarrier barrier = new CyclicBarrier(3,new Runnable(){//接受一个Runnable任务，这个任务只有最后一个到达barrier点的线程执行一次。
			public void run() {
				try {
					Thread.sleep((int)(Math.random()*1000));
					System.out.println("全部旅行团达到，准备去往下一个目的地");
				} catch (InterruptedException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
			}
		});
		ExecutorService service = Executors.newFixedThreadPool(3);
		service.submit(new Tour(timeWalk,barrier,"WalkTour"));//线程1
		service.submit(new Tour(timeSelf,barrier,"SelfTour"));//线程2
		service.submit(new Tour(timeBus,barrier,"BusTour"));  //线程3
		service.shutdown();
	}

}
